#include <stdio.h>
#include <iostream>
#include <sys/types.h>
#include <sys/socket.h>
#include <netinet/in.h>
#include <netdb.h>
#include <stdlib.h>
#include <string.h>
#include <errno.h>

using namespace std;

#define SERVER_PORT 13456
#define MAX_LINE 256

void sequencer (string);
void client (string, string);

int main(int argc, char * argv[])
{
	string leaderName;
	string userName;
	string connState;
	
	if (argc==2)
	{
		userName=argv[1];
		sequencer (userName);
	}
	else if (argc==3)
	{
		userName=argv[1];
		connState=argv[2];
	}
	else
	{
		printf("Invalid Arguments \n");
	}
	return 0;
}

void client (string userName, string connState)
{
	struct hostent *hp;
	struct sockaddr_in seq;
	char *host;
	char buf[MAX_LINE];
	int s;
	int len;
	socklen_t sin_len;

	/*translate host name into peer's IP address */
		
	hp = gethostbyname(host);
	if (!hp) {
		fprintf (stderr, "UDP duplex-talk: unknown host: %s\n", host);
		exit(1);
	}
	
	/* build address data structure */
	bzero((char *)&seq, sizeof(seq));
	seq.sin_family = AF_INET;
	bcopy(hp->h_addr, (char *)&seq.sin_addr, hp->h_length);
	seq.sin_port= htons (SERVER_PORT);
	
	/* active open */
	if ((s= socket(AF_INET, SOCK_DGRAM, 0)) <0) {
		perror("UDP duplex-talk: socket");
		exit(1);
	}
	
	sin_len= sizeof(seq);
	
	/* main loop: get and send lines of text */
	while (fgets(buf, sizeof(buf),stdin)){
		buf[MAX_LINE-1]='\0';
		len = strlen(buf)+1;
		if (sendto(s,buf,len,0,(struct sockaddr *)&seq, sin_len)<0){
			printf("UDP duplex-talk: %s\n", strerror(errno));
		}
		
		if (recvfrom(s,buf,sizeof(buf),0,(struct sockaddr *)&seq, &sin_len)<0){
			printf("UDP duplex-talk: %s\n", strerror(errno));
		}
		fputs(buf,stdout);
	}	
}

void sequencer (string userName)
{
	struct sockaddr_in seq, client;

	char buf[MAX_LINE];
	char tempbuf[MAX_LINE];
	int len;
	int s;
	socklen_t cli_len;
	
	printf("Succeeded, Current Users:\n");
	cout<<userName;

	/* build address data structure */
	bzero((char *)&seq, sizeof(seq));
	seq.sin_family = AF_INET;
	seq.sin_addr.s_addr = INADDR_ANY;
	seq.sin_port = htons(SERVER_PORT);
	
	/* setup passive open */
	if ((s= socket(AF_INET,SOCK_DGRAM,0))<0){
		perror("UDP duplex-talk: socket");
		exit(1);
	}
	
	if ((bind(s,(struct sockaddr *)&seq, sizeof(seq)))<0){
		perror("UDP duplex-talk: bind");
		exit(1);
	}
	
	cli_len=sizeof(client);
	
	/*wait for connection, then receive and print text */
	while (1){
		if (recvfrom(s,buf,sizeof(buf),0,(struct sockaddr *)&client, &cli_len)<0){
			printf("UDP duplex-talk: %s\n", strerror(errno));
		}
		
		fputs(buf,stdout);	 	
		strcpy(tempbuf,buf);
		//strcpy(buf,userName);
		strcat(buf,tempbuf);

		if (sendto(s,buf,sizeof(buf),0,(struct sockaddr *)&client, cli_len)<0){
			printf( "UDP duplex-talk: %s\n", strerror(errno));
		}
	}
	close (s);
}
